from django.shortcuts import render
from rest_framework.views import APIView
from rest_framework.response import Response
from meiduo01.models import *
from .ser import *


# Create your views here.

def xTree(datas):
    list = []
    tree = {}
    for i in datas:
        tree[i['id']] = i  # i 得到所有的数据 OrderedDict([('id', 9), ('create_time', '2021-10-07T01:15:07.284932Z'),
        # ('update_time', '2021-10-07T01:15:07.284932Z'), ('name', 'oppo R17'),
        # ('pic', '/media/FC919885C24599C20B874176C07B5709.jpg'),
        # ('level', 3), ('top_parent', 7), ('parent', 8)])

    for i in datas:
        parent = i['parent']
        if not parent:
            list.append(i)  # 里边添加的是一级分类

        else:
            if 'son' not in tree[parent]:  # 这里只剩下二三级分类
                # print(tree[parent])  #这获取到的是添加到字典里的类别
                tree[parent]['son'] = []
            tree[parent]['son'].append(i)

    return list


# 一二三级商品展示
# 一二三  三层级数据结构 一级下二级 二级下三级
# [id:'',name:'',son:[id:'',name:'',son:[id:'',name:'']]]
# 一 二三 2层数据结构 一级下二级 一级下三级 一级下所有商品
# [id:'',name:'',two:[id:'',name:''],three:[id:'',name:'']]
class HomeManage(APIView):
    def get(self, request):

        # #方法二  无限分级  配合上边xTree使用
        # cate = Category.objects.all()
        #
        # ser = HomeManageSer(cate,many=True)
        # list = xTree(ser.data)  #传值到xtree函数中计算返回一个list数据
        #
        # # 查询一级分类，一级下面的二级，一级下面的三级，一级下面所有的商品
        #
        #
        #
        # return Response({"code": 200, 'catelist': list})

        # 方法一 比较笨重
        # 获取一级
        cates = Category.objects.filter(parent_id__isnull=True).all()
        # print(cates)
        lst = []
        for i in cates:
            # print(i)
            dic = {}
            dic['id'] = i.id
            dic['name'] = i.name
            # print(dic)
            # 读取二级
            two = i.subs.all()  # i是一级分类  这一步是查看所有一级分类里的数据 用了反向查询
            # 遍历二级 获取三级
            twolst = []
            for j in two:
                twodic = {}
                twodic['id'] = j.id
                twodic['name'] = j.name
                # print(twodic)
                three = j.subs.all()  # j是二级分类 通过二级获取三级分类
                # 应因为一二级都是用字典添加可以print出来 三级不是 所以需要序列化器展示
                ser = HomeManageSer(three, many=True)

                # 二级分类里加了一个键 里边储存的是三级级分类所有内容
                twodic['subs'] = ser.data
                # 把三级分类里的数据加到二级分类列表中
                twolst.append(twodic)

            # 一级分类里加了一个键 里边储存的是二级分类所有内容
            dic['subs'] = twolst
            lst.append(dic)

        # 定义列表放三层结构 ， 定义字典添加二三级
        lst1 = []
        # 获取一级分类数据
        for i in cates:
            dic1 = {}
            dic1['id'] = i.id
            dic1['name'] = i.name
            dic1['pic'] = str(i.pic)
            # print(dic1)
            # 获取二级分类 用反查询
            two = i.subs.all()
            twoser = HomeManageSer(two, many=True)
            dic1['two'] = twoser.data
            # 获取三级分类 利用反查询
            three = Category.objects.filter(top_parent=i.id, level=3).all()
            threeser = HomeManageSer(three, many=True)
            dic1['three'] = threeser.data

            # 获取排序类型 和一级分类id
            sorted = request.GET.get('sorted')
            topid = request.GET.get('topid')

            # 获取商品
            goods = Goods.objects.filter(category1_id=i.id, home_show=1).all()
            if sorted:
                if int(topid) == int(i.id):
                    goods = Goods.objects.filter(category1_id=i.id, home_show=1).order_by('-' + sorted).all()

            goodsser = GoodsSer(goods, many=True)
            dic1['goods'] = goodsser.data
            lst1.append(dic1)

        return Response({"code": 200, 'catelist': lst, 'goodslist': lst1})


# 获取商品详情展示
class DetailManage(APIView):
    def get(self, request):
        # 获取商品id
        id = request.GET.get('id')

        # 查找商品
        goods = Goods.objects.filter(id=id).first()
        ser = GoodsSer(goods)

        return Response({'code': 200, 'list': ser.data})

    # 添加到购物车
    def post(self, request):
        # 判断是否在购物车里有数据 有数量相加  无添加新数据
        userid = request.data.get('user')
        goods = request.data.get('goods')
        number = request.data.get('number')
        cart = Cart.objects.filter(user_id=userid, goods_id=goods).first()
        if cart:
            cart.number += number
            cart.save()
            return Response({'code': 200})
        else:
            ser = CartSer(data=request.data)
            if ser.is_valid():
                ser.save()
                return Response({'code': 200})
            else:
                print(ser.errors)
                return Response({'code': 10100})


# 展示购物车   内含 单选 多选 单选全选但是全选没选择
class ShowCart(APIView):
    # 展示购物车
    def get(self, request):
        userid = request.GET.get('userid')
        cart = Cart.objects.filter(user_id=userid).all()
        ser = ShowCartSer(cart, many=True)

        # 只要单选框有一个没勾全选不亮  计算
        totalcount = 0  # 总价
        totalnum = 0  # 总数量
        totalall = 0  # 点击全选单选都不会改变的总数量
        allcheck = True
        for i in ser.data:
            totalall += int(i['number'])
            if i['is_checked'] == True:
                totalcount += int(i['number']) * float(i['goods']['price'])
                totalnum += int(i['number'])
            if i['is_checked'] == False:
                allcheck = False

        return Response(
            {'code': 200, 'list': ser.data, 'allcheck': allcheck, 'totalcount': totalcount, 'totalnum': totalnum,
             'totalall': totalall})

    # 删除购物车数据
    def delete(self, request):
        # 获取用户id 和商品id
        id = request.GET.get('id')
        Cart.objects.filter(id=id).delete()
        return Response({'code': 200})

    # 单选 只需要知道修改那条数据的状态
    def put(self, request):
        id = request.data.get('id')
        cart = Cart.objects.filter(id=id).first()
        if cart.is_checked == True:
            cart.is_checked = False
            cart.save()
        else:
            cart.is_checked = True
            cart.save()
        return Response({"code": 200})

    # 全选  需要知道用户的所有数据修改
    def post(self, request):
        userid = request.data.get('userid')
        allcheck = request.data.get('allcheck')
        if allcheck == True:
            Cart.objects.filter(user_id=userid).update(is_checked=True)
        else:
            Cart.objects.filter(user_id=userid).update(is_checked=False)

        return Response({'code': 200})


# 数量加减
class AddSubM(APIView):
    # 数量的增减
    def put(self, request):
        type = request.data.get('type')
        asid = request.data.get('asid')
        count = request.data.get('count')
        cart = Cart.objects.filter(id=asid).first()
        if type == 1:
            cart.number += 1

        elif type == 2:
            if cart.number > 1:
                cart.number -= 1
        elif type == 3:
            cart.number = int(count)
        cart.save()
        return Response({'code': 200})


import datetime
import random
from django.db import transaction  #事物
from meiduo01.ser import ShowaddressSer

# 订单提交页价格和数量
class GetCartGoods(APIView):
    def get(self, request):
        # 获取用户id
        userid = request.GET.get('userid')
        # 根据用户id is_checked=true找到勾选的数据
        cart = Cart.objects.filter(user_id=userid, is_checked=True).all()
        ser = ShowCartSer(cart, many=True)  # 应为数量没在cart里 要用嵌套序列化器
        # 找到 价格 和数量
        total = 0
        tmoney = 0
        for i in ser.data:
            total += i['number']
            tmoney += i['number'] * float(i['goods']['price'])
        # 返回
        return Response({'code': 200, 'total': total, 'tmoney': tmoney, 'list': ser.data})

    # 提交订单
    @transaction.atomic()
    def post(self, request):
        userid = request.data.get('userid')
        addressid = request.data.get('addressid')
        pay_type = request.data.get('pay_type')
        # 根据userid check是true获取购物车信息
        cart = Cart.objects.filter(user_id=userid,is_checked=True).all()
        cartser = ShowCartSer(cart,many=True)
        # 遍历购物车
        total_amount = 0
        for i in cartser.data:
            total_amount += i['number'] * float(i['goods']['price'])

        # 生成订单号  时间加用户id加随机数
        order_on = datetime.datetime.strftime(datetime.datetime.now(),'%Y%M%D%H%M%S')+str(userid)+str(random.randint(1000,9999))
        # print(order_on)
        # 查找地址构造地址信息 地址有地市区
        addreses =Address.objects.filter(id=addressid).first()
        addresss = ShowaddressSer(addreses).data
        addressStr =  str(addresss['province'])+' '+str(addresss['city'])+' '+str(addresss['area'])+' '+str(addresss['address'])+' '+str(addresss['receive'])+' '+str(addresss['mobile'])
        # 调用序列化器添加订单

        datam = {'order_no':order_on,'user':userid,'address':addressStr,'total_amount':total_amount,'pay_method':pay_type}
        print(datam)
        sid = transaction.savepoint()
        try:
            ser = OrdernoSer(data=datam)

            if ser.is_valid():
                ser.save()
                # 调用序列化器添加订单详情
                for i in cartser.data:
                    detailorder = {'order':order_on,'goods':i['goods']['id'],'goodsname':i['goods']['name'],'images':i['goods']['pic'],'count':i['number'],'price':i['goods']['price'],'user':userid}
                    detailser = OrderdetailSer(data=detailorder)
                    if detailser.is_valid():
                        detailser.save()
            # 购物车删除已经生成订单的记录
            Cart.objects.filter(user_id=userid, is_checked=True).delete()
            transaction.savepoint_commit(sid)
        # 返回结果
            return Response({'code': 200, 'order_no': order_on, 'tmoney': total_amount})
        except:
            transaction.savepoint_rollback(sid)
            return Response({'code': 20010})
